ããã³ããšã³ãã®ã³ã³ãã³ãã»ãã¥ãªãã£ããªã·ãŒ(CSP)éååæãæ·±æãããã°ããŒãã«ãªWebã¢ããªã±ãŒã·ã§ã³ã®ã»ãã¥ãªãã£ã€ãã³ãè§£æãç£èŠãããã³ç·©åæŠç¥ã«çŠç¹ãåœãŠãŸãã
ããã³ããšã³ãã®ã³ã³ãã³ãã»ãã¥ãªãã£ããªã·ãŒéååæïŒã»ãã¥ãªãã£ã€ãã³ãè§£æ
仿¥ã®è åšã®ç¶æ³ã«ãããŠãWebã¢ããªã±ãŒã·ã§ã³ã®ã»ãã¥ãªãã£ã¯æéèŠã§ããã¯ãã¹ãµã€ãã¹ã¯ãªããã£ã³ã°ïŒXSSïŒãå«ãæ§ã ãªæ»æã«å¯Ÿããæã广çãªé²åŸ¡çã®äžã€ããã³ã³ãã³ãã»ãã¥ãªãã£ããªã·ãŒïŒCSPïŒã§ããCSPã¯ãXSSãããŒã¿ã€ã³ãžã§ã¯ã·ã§ã³æ»æãªã©ãç¹å®ã®çš®é¡ã®æ»æãæ€ç¥ããç·©åããã®ã«åœ¹ç«ã€è¿œå ã®ã»ãã¥ãªãã£å±€ã§ãããããã®æ»æã¯ãããŒã¿çé£ãããµã€ãã®æ¹ããããã«ãŠã§ã¢ã®é åžãŸã§ãããããç®çã«äœ¿çšãããŸãã
ããããåã«CSPãå®è£ ããã ãã§ã¯äžååã§ããã¢ããªã±ãŒã·ã§ã³ã®ã»ãã¥ãªãã£äœå¶ãçè§£ããæœåšçãªè匱æ§ãç¹å®ããããªã·ãŒã埮調æŽããããã«ã¯ãCSPéåãç©æ¥µçã«ç£èŠã»åæããå¿ èŠããããŸãããã®èšäºã§ã¯ãããã³ããšã³ãã®CSPéååæã«é¢ããå æ¬çãªã¬ã€ããæäŸããã»ãã¥ãªãã£ã€ãã³ãè§£æãšæ¹åã®ããã®å®è·µçãªæŠç¥ã«çŠç¹ãåœãŠãŸãããŸãã倿§ãªéçºç°å¢ã§CSPã管çããããã®ã°ããŒãã«ãªæå³åããšãã¹ããã©ã¯ãã£ã¹ã«ã€ããŠãæ¢æ±ããŸãã
ã³ã³ãã³ãã»ãã¥ãªãã£ããªã·ãŒïŒCSPïŒãšã¯ïŒ
ã³ã³ãã³ãã»ãã¥ãªãã£ããªã·ãŒïŒCSPïŒã¯ããŠãŒã¶ãŒãšãŒãžã§ã³ããç¹å®ã®ããŒãžã«å¯ŸããŠèªã¿èŸŒãããšãèš±å¯ããããªãœãŒã¹ãWebéçºè ãå¶åŸ¡ã§ããããã«ãããHTTPã¬ã¹ãã³ã¹ããããŒãšããŠå®çŸ©ãããã»ãã¥ãªãã£æšæºã§ããä¿¡é Œã§ãããœãŒã¹ã®ãã¯ã€ããªã¹ããå®çŸ©ããããšã«ãããWebã¢ããªã±ãŒã·ã§ã³ã«æªæã®ããã³ã³ãã³ããæ³šå ¥ããããªã¹ã¯ãå€§å¹ ã«åæžã§ããŸããCSPã¯ãæå®ããããœãŒã¹ããã®ã¿ã¹ã¯ãªãããå®è¡ããç»åãã¹ã¿ã€ã«ã·ãŒãããã®ä»ã®ãªãœãŒã¹ãèªã¿èŸŒããããã©ãŠã¶ã«æç€ºããããšã§æ©èœããŸãã
CSPã®äž»èŠãªãã£ã¬ã¯ãã£ãïŒ
- `default-src`: ä»ã®ãã§ãããã£ã¬ã¯ãã£ãã®ãã©ãŒã«ããã¯ãšããŠæ©èœããŸããç¹å®ã®ãªãœãŒã¹ã¿ã€ããå®çŸ©ãããŠããªãå Žåããã®ãã£ã¬ã¯ãã£ãã䜿çšãããŸãã
- `script-src`: JavaScriptã®æå¹ãªãœãŒã¹ãæå®ããŸãã
- `style-src`: CSSã¹ã¿ã€ã«ã·ãŒãã®æå¹ãªãœãŒã¹ãæå®ããŸãã
- `img-src`: ç»åã®æå¹ãªãœãŒã¹ãæå®ããŸãã
- `connect-src`: fetchãXMLHttpRequestãWebSocketãããã³EventSourceæ¥ç¶ã®æå¹ãªãœãŒã¹ãæå®ããŸãã
- `font-src`: ãã©ã³ãã®æå¹ãªãœãŒã¹ãæå®ããŸãã
- `media-src`: é³å£°ãåç»ãªã©ã®ã¡ãã£ã¢ãèªã¿èŸŒãããã®æå¹ãªãœãŒã¹ãæå®ããŸãã
- `object-src`: Flashãªã©ã®ãã©ã°ã€ã³ã®æå¹ãªãœãŒã¹ãæå®ããŸããïŒäžè¬çã«ã¯ãããã 'none' ã«èšå®ããŠãã©ã°ã€ã³ãå®å šã«ç¡å¹ã«ããããšãæåã§ããïŒ
- `base-uri`: ããã¥ã¡ã³ãã®`
`èŠçŽ ã§äœ¿çšã§ããæå¹ãªURLãæå®ããŸãã - `form-action`: ãã©ãŒã éä¿¡ã®ããã®æå¹ãªãšã³ããã€ã³ããæå®ããŸãã
- `frame-ancestors`: ``ã`
- `report-uri` (éæšå¥š): ãã©ãŠã¶ãCSPéåã«é¢ããã¬ããŒããéä¿¡ãã¹ãURLãæå®ããŸãã代ããã«`report-to`ã®äœ¿çšãæ€èšããŠãã ããã
- `report-to`: ãã©ãŠã¶ãCSPéåã«é¢ããã¬ããŒããéä¿¡ããããã«äœ¿çšãã¹ãã`Report-To`ããããŒãä»ããŠèšå®ãããååä»ããšã³ããã€ã³ããæå®ããŸããããã¯`report-uri`ã®çŸä»£çãªä»£æ¿ææ®µã§ãã
- `upgrade-insecure-requests`: ãŠãŒã¶ãŒãšãŒãžã§ã³ãã«ããµã€ãã®ãã¹ãŠã®å®å šã§ãªãURLïŒHTTPã§æäŸããããã®ïŒããå®å šãªURLïŒHTTPSã§æäŸããããã®ïŒã«çœ®ãæãããããã®ããã«æ±ãããæç€ºããŸãããã®ãã£ã¬ã¯ãã£ãã¯ãHTTPSã«ç§»è¡äžã®ãŠã§ããµã€ãã察象ãšããŠããŸãã
CSPããããŒã®äŸïŒ
`Content-Security-Policy: default-src 'self'; script-src 'self' https://example.com; style-src 'self' 'unsafe-inline'; img-src 'self' data:; report-to csp-endpoint;`
ãã®ããªã·ãŒã¯ãåäžãªãªãžã³ïŒ`'self'`ïŒããã®ãªãœãŒã¹èªã¿èŸŒã¿ã`https://example.com`ããã®JavaScriptãã€ã³ã©ã€ã³ã¹ã¿ã€ã«ãåäžãªãªãžã³ããã³ããŒã¿URIããã®ç»åããããŠ`csp-endpoint`ãšããååã®ïŒ`Report-To`ããããŒã§èšå®ãããïŒã¬ããŒããšã³ããã€ã³ããæå®ããããšãèš±å¯ããŸãã
ãªãCSPéååæãéèŠãªã®ãïŒ
é©åã«èšå®ãããCSPã¯ã»ãã¥ãªãã£ãå€§å¹ ã«åŒ·åã§ããŸããããã®å¹æã¯éåã¬ããŒããç©æ¥µçã«ç£èŠã»åæããããšã«ããã£ãŠããŸãããããã®ã¬ããŒããç¡èŠãããšã誀ã£ãå®å¿æã«ã€ãªãããå®éã®è匱æ§ã«å¯ŸåŠããæ©äŒãéãå¯èœæ§ããããŸããCSPéååæãéèŠãªçç±ã¯æ¬¡ã®ãšããã§ãïŒ
- XSSã®è©Šã¿ãç¹å®ããïŒ CSPéåã¯ããã°ãã°è©Šã¿ãããXSSæ»æã瀺åããŸãããããã®ã¬ããŒããåæããããšã§ãæªæã®ããæŽ»åã害ãåãŒãåã«æ€ç¥ãã察å¿ããããšãã§ããŸãã
- ããªã·ãŒã®åŒ±ç¹ãæããã«ããïŒ éåã¬ããŒãã¯ãCSPèšå®ã®ã®ã£ãããæããã«ããŸããã©ã®ãªãœãŒã¹ããããã¯ãããŠããããç¹å®ããããšã§ãæ£åœãªæ©èœãå£ãããšãªãããã广çãªããªã·ãŒã«æŽç·Žãããããšãã§ããŸãã
- æ£åœãªã³ãŒãã®åé¡ããããã°ããïŒ æã«ã¯ãæå³ããCSPã«éåããæ£åœãªã³ãŒãã«ãã£ãŠéåãåŒãèµ·ããããããšããããŸããã¬ããŒããåæããããšã§ããããã®åé¡ãç¹å®ããä¿®æ£ããã®ã«åœ¹ç«ã¡ãŸããäŸãã°ãéçºè ã誀ã£ãŠã€ã³ã©ã€ã³ã¹ã¯ãªãããCSSã«ãŒã«ãå«ããŠããŸããããã峿 ŒãªCSPã«ãã£ãŠãããã¯ãããå¯èœæ§ããããŸãã
- ãµãŒãããŒãã£ã®çµ±åãç£èŠããïŒ ãµãŒãããŒãã£ã®ã©ã€ãã©ãªããµãŒãã¹ã¯ãã»ãã¥ãªãã£ãªã¹ã¯ãããããå¯èœæ§ããããŸããCSPéåã¬ããŒãã¯ããããã®çµ±åã®æåã«é¢ããæŽå¯ãæäŸããããããã»ãã¥ãªãã£ããªã·ãŒã«æºæ ããŠããããšã確èªããã®ã«åœ¹ç«ã¡ãŸããå€ãã®çµç¹ã§ã¯çŸåšãã»ãã¥ãªãã£è©äŸ¡ã®äžç°ãšããŠããµãŒãããŒãã£ãã³ããŒã«CSPã³ã³ãã©ã€ã¢ã³ã¹ã«é¢ããæ å ±æäŸã矩åä»ããŠããŸãã
- ã³ã³ãã©ã€ã¢ã³ã¹ãšç£æ»ïŒ å€ãã®èŠå¶ãæ¥çæšæºã§ã¯ãå ç¢ãªã»ãã¥ãªãã£å¯Ÿçãæ±ããããŠããŸããCSPãšãã®ç£èŠã¯ãã³ã³ãã©ã€ã¢ã³ã¹ã蚌æããããã®éèŠãªèŠçŽ ãšãªãåŸãŸããCSPéåã®èšé²ãšããã«å¯Ÿãã察å¿ãç¶æããããšã¯ãã»ãã¥ãªãã£ç£æ»æã«äŸ¡å€ããããŸãã
CSPã¬ããŒãã®èšå®
CSPéåãåæããåã«ãæå®ããããšã³ããã€ã³ãã«ã¬ããŒããéä¿¡ããããã«ãµãŒããŒãèšå®ããå¿ èŠããããŸããçŸä»£ã®CSPã¬ããŒãã¯`Report-To`ããããŒã掻çšããŠãããããã¯éæšå¥šã®`report-uri`ãã£ã¬ã¯ãã£ããšæ¯èŒããŠãããé«ãæè»æ§ãšä¿¡é Œæ§ãæäŸããŸãã
ã¹ããã1ïŒ`Report-To`ããããŒã®èšå®ïŒ
`Report-To`ããããŒã¯ã1ã€ä»¥äžã®ã¬ããŒããšã³ããã€ã³ããå®çŸ©ããŸããåãšã³ããã€ã³ãã«ã¯ãååãURLãããã³ãªãã·ã§ã³ã®æå¹æéããããŸãã
äŸïŒ
`Report-To: {"group":"csp-endpoint","max_age":31536000,"endpoints":[{"url":"https://your-reporting-service.com/csp-report"}],"include_subdomains":true}`
- `group`: ã¬ããŒããšã³ããã€ã³ãã®ååïŒäŸïŒãcsp-endpointãïŒããã®ååã¯ãCSPããããŒã®`report-to`ãã£ã¬ã¯ãã£ãã§åç §ãããŸãã
- `max_age`: ãšã³ããã€ã³ãèšå®ã®æå¹æéïŒç§åäœïŒããã©ãŠã¶ã¯ãã®æéããšã³ããã€ã³ãèšå®ããã£ãã·ã¥ããŸããäžè¬çãªå€ã¯31536000ç§ïŒ1幎ïŒã§ãã
- `endpoints`: ãšã³ããã€ã³ããªããžã§ã¯ãã®é åãåãªããžã§ã¯ãã¯ã¬ããŒããéä¿¡ãããã¹ãURLãæå®ããŸããåé·æ§ã®ããã«è€æ°ã®ãšã³ããã€ã³ããèšå®ã§ããŸãã
- `include_subdomains` (ãªãã·ã§ã³): `true`ã«èšå®ãããŠããå Žåãã¬ããŒãèšå®ã¯ãã¡ã€ã³ã®ãã¹ãŠã®ãµããã¡ã€ã³ã«é©çšãããŸãã
ã¹ããã2ïŒ`Content-Security-Policy`ããããŒã®èšå®ïŒ
`Content-Security-Policy`ããããŒã¯CSPããªã·ãŒãå®çŸ©ãã`Report-To`ããããŒã§å®çŸ©ãããã¬ããŒããšã³ããã€ã³ããåç §ãã`report-to`ãã£ã¬ã¯ãã£ããå«ã¿ãŸãã
äŸïŒ
`Content-Security-Policy: default-src 'self'; script-src 'self' https://example.com; report-to csp-endpoint;`
ã¹ããã3ïŒã¬ããŒããšã³ããã€ã³ãã®ã»ããã¢ããïŒ
CSPéåã¬ããŒããåä¿¡ããŠåŠçãããµãŒããŒãµã€ãã®ãšã³ããã€ã³ããäœæããå¿ èŠããããŸãããã®ãšã³ããã€ã³ãã¯JSONããŒã¿ãåŠçããåæã®ããã«ã¬ããŒããä¿åã§ããå¿ èŠããããŸããå ·äœçãªå®è£ ã¯ããµãŒããŒãµã€ãã®ãã¯ãããžãŒïŒäŸïŒNode.jsãPythonãJavaïŒã«ãã£ãŠç°ãªããŸãã
äŸïŒNode.jsãšExpressïŒïŒ
const express = require('express');
const bodyParser = require('body-parser');
const app = express();
app.use(bodyParser.json());
app.post('/csp-report', (req, res) => {
const report = req.body['csp-report'];
console.log('CSP Violation Report:', report);
// ã¬ããŒããããŒã¿ããŒã¹ããã°ãã¡ã€ã«ã«ä¿å
res.status(204).end(); // 204 No Contentã¹ããŒã¿ã¹ã§å¿ç
});
const port = 3000;
app.listen(port, () => {
console.log(`Server listening on port ${port}`);
});
ã¹ããã4ïŒãã¹ãçšã«`Content-Security-Policy-Report-Only`ãæ€èšããïŒ
CSPã匷å¶ããåã«ãã¬ããŒãå°çšã¢ãŒãã§ãã¹ãããããšããå§ãããŸããããã«ããããªãœãŒã¹ããããã¯ããããšãªãéåãç£èŠã§ããŸãã`Content-Security-Policy`ã®ä»£ããã«`Content-Security-Policy-Report-Only`ããããŒã䜿çšããŸããéåã¯ã¬ããŒããšã³ããã€ã³ãã«å ±åãããŸããããã©ãŠã¶ã¯ããªã·ãŒã匷å¶ããŸããã
äŸïŒ
`Content-Security-Policy-Report-Only: default-src 'self'; script-src 'self' https://example.com; report-to csp-endpoint;`
CSPéåã¬ããŒãã®åæ
CSPã¬ããŒããèšå®ãããšãéåã¬ããŒãã®åä¿¡ãå§ãŸããŸãããããã®ã¬ããŒãã¯ãéåã«é¢ããæ å ±ãå«ãJSONãªããžã§ã¯ãã§ããã¬ããŒãã®æ§é ã¯CSP仿§ã«ãã£ãŠå®çŸ©ãããŠããŸãã
CSPéåã¬ããŒãã®äŸïŒ
{
"csp-report": {
"document-uri": "https://example.com/page.html",
"referrer": "https://attacker.com",
"violated-directive": "script-src 'self' https://example.com",
"effective-directive": "script-src",
"original-policy": "default-src 'self'; script-src 'self' https://example.com; report-to csp-endpoint;",
"disposition": "report",
"blocked-uri": "https://attacker.com/evil.js",
"status-code": 200,
"script-sample": "",
"source-file": "https://attacker.com/evil.js",
"line-number": 1,
"column-number": 1
}
}
CSPéåã¬ããŒãã®äž»èŠãªãã£ãŒã«ãïŒ
- `document-uri`: éåãçºçããããã¥ã¡ã³ãã®URIã
- `referrer`: åç §å ããŒãžã®URIïŒããããã°ïŒã
- `violated-directive`: éåããCSPãã£ã¬ã¯ãã£ãã
- `effective-directive`: ãã©ãŒã«ããã¯ã¡ã«ããºã ãèæ ®ããŠå®éã«é©çšããããã£ã¬ã¯ãã£ãã
- `original-policy`: æå¹ã§ãã£ãå®å šãªCSPããªã·ãŒã
- `disposition`: éåã匷å¶ããããïŒ`"enforce"`ïŒãå ±åã®ã¿ãïŒ`"report"`ïŒã瀺ããŸãã
- `blocked-uri`: ãããã¯ããããªãœãŒã¹ã®URIã
- `status-code`: ãããã¯ããããªãœãŒã¹ã®HTTPã¹ããŒã¿ã¹ã³ãŒãã
- `script-sample`: ãããã¯ãããã¹ã¯ãªããã®ã¹ããããïŒè©²åœããå ŽåïŒããã©ãŠã¶ã¯ã»ãã¥ãªãã£äžã®çç±ããã¹ã¯ãªãããµã³ãã«ã®äžéšãç·šéããããšããããŸãã
- `source-file`: éåãçºçãããœãŒã¹ãã¡ã€ã«ïŒå©çšå¯èœãªå ŽåïŒã
- `line-number`: éåãçºçãããœãŒã¹ãã¡ã€ã«å ã®è¡çªå·ã
- `column-number`: éåãçºçãããœãŒã¹ãã¡ã€ã«å ã®åçªå·ã
广çãªã»ãã¥ãªãã£ã€ãã³ãè§£æã®æé
CSPéåã¬ããŒãã®åæã¯ãæ§é åãããã¢ãããŒããå¿ èŠãšããç¶ç¶çãªããã»ã¹ã§ãã以äžã«ãCSPéåããŒã¿ã«åºã¥ãã»ãã¥ãªãã£ã€ãã³ãã广çã«åæããããã®ã¹ããããã€ã¹ãããã¬ã€ãã瀺ããŸãïŒ
- æ·±å»åºŠã«åºã¥ããŠã¬ããŒããåªå é äœä»ãããïŒ æœåšçãªXSSæ»æããã®ä»ã®æ·±å»ãªã»ãã¥ãªãã£ãªã¹ã¯ã瀺ãéåã«çŠç¹ãåœãŠãŸããäŸãã°ãæªç¥ãŸãã¯ä¿¡é Œã§ããªããœãŒã¹ããã®ãããã¯ãããURIãæã€éåã¯ãçŽã¡ã«èª¿æ»ããå¿ èŠããããŸãã
- æ ¹æ¬åå ãç¹å®ããïŒ ãªãéåãçºçããã®ãã倿ããŸããèšå®ãã¹ã«ãã£ãŠãããã¯ãããŠããæ£åœãªãªãœãŒã¹ãªã®ãããããšãå®è¡ã詊ã¿ãŠããæªæã®ããã¹ã¯ãªãããªã®ãïŒ `blocked-uri`ã`violated-directive`ãããã³`referrer`ãã£ãŒã«ããèŠãŠãéåã®æèãçè§£ããŸãã
- éåãåé¡ããïŒ æ ¹æ¬åå ã«åºã¥ããŠéåãã«ããŽãªã«ã°ã«ãŒãåããŸããããã«ããããã¿ãŒã³ãç¹å®ããä¿®æ£äœæ¥ã®åªå é äœä»ãã«åœ¹ç«ã¡ãŸããäžè¬çãªã«ããŽãªã«ã¯æ¬¡ã®ãã®ããããŸãïŒ
- èšå®ãã¹ïŒ äžæ£ãªCSPãã£ã¬ã¯ãã£ããŸãã¯æ¬ èœããäŸå€ã«ãã£ãŠåŒãèµ·ããããéåã
- æ£åœãªã³ãŒãã®åé¡ïŒ ã€ã³ã©ã€ã³ã¹ã¯ãªãããã¹ã¿ã€ã«ããŸãã¯CSPã«éåããã³ãŒãã«ãã£ãŠåŒãèµ·ããããéåã
- ãµãŒãããŒãã£ã®åé¡ïŒ ãµãŒãããŒãã£ã®ã©ã€ãã©ãªããµãŒãã¹ã«ãã£ãŠåŒãèµ·ããããéåã
- XSSã®è©Šã¿ïŒ æœåšçãªXSSæ»æã瀺ãéåã
- äžå¯©ãªæŽ»åã調æ»ããïŒ éåãXSSã®è©Šã¿ã§ãããšæãããå Žåã¯ã培åºçã«èª¿æ»ããŸãã`referrer`ã`blocked-uri`ãããã³`script-sample`ãã£ãŒã«ããèŠãŠãæ»æè ã®æå³ãçè§£ããŸãããµãŒããŒãã°ãä»ã®ã»ãã¥ãªãã£ç£èŠããŒã«ã§é¢é£ããæŽ»åã確èªããŸãã
- éåãä¿®æ£ããïŒ æ ¹æ¬åå ã«åºã¥ããŠãéåãä¿®æ£ããããã®æªçœ®ãè¬ããŸããããã«ã¯ä»¥äžãå«ãŸããå ŽåããããŸãïŒ
- CSPã®æŽæ°ïŒ ãããã¯ãããŠããæ£åœãªãªãœãŒã¹ãèš±å¯ããããã«CSPã倿ŽããŸããããªã·ãŒãäžå¿ èŠã«åŒ±ããªãããã«æ³šæããŠãã ããã
- ã³ãŒãã®ä¿®æ£ïŒ ã€ã³ã©ã€ã³ã¹ã¯ãªãããã¹ã¿ã€ã«ãåé€ããããCSPã«æºæ ããããã«ã³ãŒããä¿®æ£ããŸãã
- ãµãŒãããŒãã£ã©ã€ãã©ãªã®æŽæ°ïŒ ãµãŒãããŒãã£ã©ã€ãã©ãªãææ°ããŒãžã§ã³ã«æŽæ°ããŸããããã«ã¯ã»ãã¥ãªãã£ä¿®æ£ãå«ãŸããŠããå ŽåããããŸãã
- æªæã®ããæŽ»åã®ãããã¯ïŒ éåã¬ããŒãã®æ å ±ã«åºã¥ããŠãæªæã®ãããªã¯ãšã¹ãããŠãŒã¶ãŒããããã¯ããŸãã
- 倿Žããã¹ãããïŒ CSPãã³ãŒãã«å€æŽãå ããåŸãã¢ããªã±ãŒã·ã§ã³ã培åºçã«ãã¹ãããŠã倿Žãæ°ããªåé¡ãåŒãèµ·ãããŠããªãããšã確èªããŸãã`Content-Security-Policy-Report-Only`ããããŒã䜿çšããŠãé匷å¶ã¢ãŒãã§å€æŽããã¹ãããŸãã
- 調æ»çµæãææžåããïŒ éåããã®æ ¹æ¬åå ãããã³è¬ããä¿®æ£æªçœ®ãææžåããŸãããã®æ å ±ã¯ãå°æ¥ã®åæãã³ã³ãã©ã€ã¢ã³ã¹ç®çã§äŸ¡å€ããããŸãã
- åæããã»ã¹ãèªååããïŒ CSPéåã¬ããŒããåæããããã«èªååããŒã«ã䜿çšããããšãæ€èšããŸãããããã®ããŒã«ã¯ããã¿ãŒã³ã®ç¹å®ãéåã®åªå é äœä»ããããã³ã¬ããŒãã®çæã«åœ¹ç«ã¡ãŸãã
å®è·µçãªäŸãšã·ããªãª
CSPéåã¬ããŒãã®åæããã»ã¹ã説æããããã«ãããã€ãã®å®è·µçãªäŸãèããŠã¿ãŸãããïŒ
ã·ããªãª1ïŒã€ã³ã©ã€ã³ã¹ã¯ãªããã®ãããã¯
éåã¬ããŒãïŒ
{
"csp-report": {
"document-uri": "https://example.com/page.html",
"violated-directive": "script-src 'self' https://example.com",
"blocked-uri": "inline",
"script-sample": ""
}
}
åæïŒ
ãã®éåã¯ãCSPãã€ã³ã©ã€ã³ã¹ã¯ãªããããããã¯ããŠããããšã瀺ããŠããŸããã€ã³ã©ã€ã³ã¹ã¯ãªããã¯ãã°ãã°ã»ãã¥ãªãã£ãªã¹ã¯ãšèŠãªããããããããã¯äžè¬çãªã·ããªãªã§ãã`script-sample`ãã£ãŒã«ãã¯ããããã¯ãããã¹ã¯ãªããã®å 容ã瀺ããŠããŸãã
ä¿®æ£ïŒ
æåã®è§£æ±ºçã¯ãã¹ã¯ãªãããå¥ã®ãã¡ã€ã«ã«ç§»åããä¿¡é Œã§ãããœãŒã¹ããèªã¿èŸŒãããšã§ãããããã¯ãnonceãŸãã¯ããã·ã¥ã䜿çšããŠç¹å®ã®ã€ã³ã©ã€ã³ã¹ã¯ãªãããèš±å¯ããããšãã§ããŸãããã ãããããã®æ¹æ³ã¯äžè¬çã«ãã¹ã¯ãªãããå¥ã®ãã¡ã€ã«ã«ç§»åãããããå®å šæ§ãäœãã§ãã
ã·ããªãª2ïŒãµãŒãããŒãã£ã©ã€ãã©ãªã®ãããã¯
éåã¬ããŒãïŒ
{
"csp-report": {
"document-uri": "https://example.com/page.html",
"violated-directive": "script-src 'self' https://example.com",
"blocked-uri": "https://cdn.example.com/library.js"
}
}
åæïŒ
ãã®éåã¯ãCSPã`https://cdn.example.com`ã§ãã¹ããããŠãããµãŒãããŒãã£ã©ã€ãã©ãªããããã¯ããŠããããšã瀺ããŠããŸããããã¯ãèšå®ãã¹ãŸãã¯ã©ã€ãã©ãªã®å Žæã®å€æŽãåå ã§ããå¯èœæ§ããããŸãã
ä¿®æ£ïŒ
CSPããã§ãã¯ããŠã`https://cdn.example.com`ã`script-src`ãã£ã¬ã¯ãã£ãã«å«ãŸããŠããããšã確èªããŸããå«ãŸããŠããå Žåã¯ãã©ã€ãã©ãªãæå®ãããURLã§ãŸã ãã¹ããããŠããããšã確èªããŸããã©ã€ãã©ãªãç§»åããå Žåã¯ãããã«å¿ããŠCSPãæŽæ°ããŸãã
ã·ããªãª3ïŒæœåšçãªXSSæ»æ
éåã¬ããŒãïŒ
{
"csp-report": {
"document-uri": "https://example.com/page.html",
"referrer": "https://attacker.com",
"violated-directive": "script-src 'self' https://example.com",
"blocked-uri": "https://attacker.com/evil.js"
}
}
åæïŒ
ãã®éåã¯ãæœåšçãªXSSæ»æã瀺ããŠãããããããæžå¿µãããŸãã`referrer`ãã£ãŒã«ãã¯ãªã¯ãšã¹ãã`https://attacker.com`ããçºä¿¡ãããããšã瀺ãã`blocked-uri`ãã£ãŒã«ãã¯CSPãåããã¡ã€ã³ããã®ã¹ã¯ãªããããããã¯ããããšã瀺ããŠããŸããããã¯ãæ»æè ãã¢ããªã±ãŒã·ã§ã³ã«æªæã®ããã³ãŒããæ³šå ¥ããããšããŠããããšã匷ã瀺åããŠããŸãã
ä¿®æ£ïŒ
çŽã¡ã«éåã調æ»ããŸãããµãŒããŒãã°ã§é¢é£ããæŽ»åã確èªããŸããæ»æè ã®IPã¢ãã¬ã¹ããããã¯ããå°æ¥ã®æ»æãé²ãããã®æªçœ®ãè¬ããŸããXSSæ»æãèš±ãå¯èœæ§ã®ããè匱æ§ããªããã³ãŒããèŠçŽããŸããå ¥åæ€èšŒãåºåãšã³ã³ãŒãã£ã³ã°ãªã©ã远å ã®ã»ãã¥ãªãã£å¯Ÿçã®å®è£ ãæ€èšããŸãã
CSPéååæã®ããã®ããŒã«
CSPéåã¬ããŒãã®åæããã»ã¹ãèªååããç°¡çŽ åããã®ã«åœ¹ç«ã€ããã€ãã®ããŒã«ããããŸãããããã®ããŒã«ã¯ã次ã®ãããªæ©èœãæäŸã§ããŸãïŒ
- éçŽãšèŠèŠåïŒ è€æ°ã®ãœãŒã¹ããã®éåã¬ããŒããéçŽããããŒã¿ãèŠèŠåããŠåŸåããã¿ãŒã³ãç¹å®ããŸãã
- ãã£ã«ã¿ãªã³ã°ãšæ€çŽ¢ïŒ `document-uri`ã`violated-directive`ã`blocked-uri`ãªã©ã®æ§ã ãªåºæºã«åºã¥ããŠã¬ããŒãããã£ã«ã¿ãªã³ã°ããã³æ€çŽ¢ããŸãã
- ã¢ã©ãŒãïŒ äžå¯©ãªéåãæ€åºããããšãã«ã¢ã©ãŒããéä¿¡ããŸãã
- ã¬ããŒãäœæïŒ ã³ã³ãã©ã€ã¢ã³ã¹ãç£æ»ç®çã§CSPéåã«é¢ããã¬ããŒããçæããŸãã
- ã»ãã¥ãªãã£æ å ±ããã³ã€ãã³ã管çïŒSIEMïŒã·ã¹ãã ãšã®çµ±åïŒ CSPéåã¬ããŒããSIEMã·ã¹ãã ã«è»¢éããäžå åãããã»ãã¥ãªãã£ç£èŠãå®çŸããŸãã
人æ°ã®ããCSPéååæããŒã«ã«ã¯ã以äžã®ãããªãã®ããããŸãïŒ
- Report URIïŒ éåã¬ããŒãã®è©³çްãªåæãšèŠèŠåãæäŸããå°çšã®CSPã¬ããŒããµãŒãã¹ã
- SentryïŒ CSPéåã®ç£èŠã«ã䜿çšã§ãã人æ°ã®ãšã©ãŒãã©ããã³ã°ããã³ããã©ãŒãã³ã¹ç£èŠãã©ãããã©ãŒã ã
- Google Security AnalyticsïŒ ä»ã®ã»ãã¥ãªãã£ããŒã¿ãšå ±ã«CSPéåã¬ããŒããåæã§ããã¯ã©ãŠãããŒã¹ã®ã»ãã¥ãªãã£åæãã©ãããã©ãŒã ã
- ã«ã¹ã¿ã ãœãªã¥ãŒã·ã§ã³ïŒ ãªãŒãã³ãœãŒã¹ã®ã©ã€ãã©ãªããã¬ãŒã ã¯ãŒã¯ã䜿çšããŠãç¬èªã®CSPéååæããŒã«ãæ§ç¯ããããšãã§ããŸãã
CSPå®è£ ã«ãããã°ããŒãã«ãªèæ ®äºé
ã°ããŒãã«ãªæèã§CSPãå®è£ ããå Žåã以äžã®ç¹ãèæ ®ããããšãäžå¯æ¬ ã§ãïŒ
- ã³ã³ãã³ãé ä¿¡ãããã¯ãŒã¯ïŒCDNïŒïŒ ã¢ããªã±ãŒã·ã§ã³ãéçãªãœãŒã¹ãé ä¿¡ããããã«CDNã䜿çšããŠããå ŽåãCDNãã¡ã€ã³ãCSPã«å«ãŸããŠããããšã確èªããŠãã ãããCDNã«ã¯å°åçãªããªãšãŒã·ã§ã³ïŒäŸïŒåç±³åãã®`cdn.example.com`ããšãŒãããåãã®`cdn.example.eu`ïŒããããããŸããCSPã¯ãããã®ããªãšãŒã·ã§ã³ã«å¯Ÿå¿ããå¿ èŠããããŸãã
- ãµãŒãããŒãã£ãµãŒãã¹ïŒ å€ãã®ãŠã§ããµã€ãã¯ãåæããŒã«ãåºåãããã¯ãŒã¯ããœãŒã·ã£ã«ã¡ãã£ã¢ãŠã£ãžã§ãããªã©ã®ãµãŒãããŒãã£ãµãŒãã¹ã«äŸåããŠããŸãããããã®ãµãŒãã¹ã䜿çšãããã¡ã€ã³ãCSPã«å«ãŸããŠããããšã確èªããŠãã ããããµãŒãããŒãã£ã®çµ±åã宿çã«èŠçŽããæ°èŠãŸãã¯å€æŽããããã¡ã€ã³ãç¹å®ããŸãã
- ããŒã«ãªãŒãŒã·ã§ã³ïŒ ã¢ããªã±ãŒã·ã§ã³ãè€æ°ã®èšèªãå°åããµããŒãããŠããå Žåãç°ãªããªãœãŒã¹ããã¡ã€ã³ã«å¯Ÿå¿ããããã«CSPã調æŽããå¿ èŠããããããããŸãããäŸãã°ãç°ãªãå°åã®CDNãããã©ã³ããç»åãèš±å¯ããå¿ èŠãããå ŽåããããŸãã
- å°åã®èŠå¶ïŒ äžéšã®åœã§ã¯ãããŒã¿ãã©ã€ãã·ãŒãšã»ãã¥ãªãã£ã«é¢ããç¹å®ã®èŠå¶ããããŸããCSPããããã®èŠå¶ã«æºæ ããŠããããšã確èªããŠãã ãããäŸãã°ã欧å·é£åã®äžè¬ããŒã¿ä¿è·èŠåïŒGDPRïŒã¯ãEUåžæ°ã®å人ããŒã¿ãä¿è·ããããšãèŠæ±ããŠããŸãã
- ç°ãªãå°åã§ã®ãã¹ãïŒ CSPãæ£ããæ©èœããæ£åœãªãªãœãŒã¹ããããã¯ããªãããšã確èªããããã«ãç°ãªãå°åã§CSPããã¹ãããŸãããã©ãŠã¶ã®éçºè ããŒã«ããªã³ã©ã€ã³ã®CSPããªããŒã¿ã䜿çšããŠããªã·ãŒãæ€èšŒããŸãã
CSP管çã®ãã¹ããã©ã¯ãã£ã¹
CSPã®ç¶ç¶çãªæå¹æ§ã確ä¿ããããã«ã以äžã®ãã¹ããã©ã¯ãã£ã¹ã«åŸã£ãŠãã ããïŒ
- 峿 Œãªããªã·ãŒããå§ããïŒ ä¿¡é Œã§ãããœãŒã¹ããã®ãªãœãŒã¹ã®ã¿ãèš±å¯ãã峿 Œãªããªã·ãŒããå§ããŸããéåã¬ããŒãã«åºã¥ããŠãå¿ èŠã«å¿ããŠåŸã ã«ããªã·ãŒãç·©åããŸãã
- ã€ã³ã©ã€ã³ã¹ã¯ãªãããšã¹ã¿ã€ã«ã«ã¯nonceãŸãã¯ããã·ã¥ã䜿çšããïŒ ã€ã³ã©ã€ã³ã¹ã¯ãªãããã¹ã¿ã€ã«ã䜿çšããªããã°ãªããªãå Žåã¯ãnonceãŸãã¯ããã·ã¥ã䜿çšããŠç¹å®ã®ã€ã³ã¹ã¿ã³ã¹ãèš±å¯ããŸããããã¯ããã¹ãŠã®ã€ã³ã©ã€ã³ã¹ã¯ãªãããã¹ã¿ã€ã«ãèš±å¯ãããããå®å šã§ãã
- `unsafe-inline`ãš`unsafe-eval`ãé¿ããïŒ ãããã®ãã£ã¬ã¯ãã£ãã¯CSPãå€§å¹ ã«åŒ±ãããããå¯èœã§ããã°é¿ããã¹ãã§ãã
- CSPã宿çã«èŠçŽããæŽæ°ããïŒ CSPããŸã æå¹ã§ãããã¢ããªã±ãŒã·ã§ã³ããµãŒãããŒãã£ã®çµ±åã®å€æŽãåæ ããŠããããšã確èªããããã«ã宿çã«CSPãèŠçŽããŸãã
- CSPã®å±éããã»ã¹ãèªååããïŒ CSP倿Žã®å±éããã»ã¹ãèªååããäžè²«æ§ã確ä¿ãããšã©ãŒã®ãªã¹ã¯ãæžãããŸãã
- CSPéåã¬ããŒããç£èŠããïŒ æœåšçãªã»ãã¥ãªãã£ãªã¹ã¯ãç¹å®ããããªã·ãŒã埮調æŽããããã«ãCSPéåã¬ããŒãã宿çã«ç£èŠããŸãã
- éçºããŒã ãæè²ããïŒ CSPãšãã®éèŠæ§ã«ã€ããŠéçºããŒã ãæè²ããŸãã圌ããCSPã«æºæ ããã³ãŒããæžãæ¹æ³ãçè§£ããŠããããšã確èªããŸãã
CSPã®æªæ¥
ã³ã³ãã³ãã»ãã¥ãªãã£ããªã·ãŒæšæºã¯ãæ°ããªã»ãã¥ãªãã£èª²é¡ã«å¯ŸåŠããããã«çµ¶ããé²åããŠããŸããCSPã«ãããæ°ããªãã¬ã³ãã«ã¯ã以äžã®ãããªãã®ããããŸãïŒ
- Trusted TypesïŒ DOMã«æ¿å ¥ãããããŒã¿ãé©åã«ãµãã¿ã€ãºãããŠããããšãä¿èšŒããããšã§ãDOMããŒã¹ã®XSSæ»æãé²ãã®ã«åœ¹ç«ã€æ°ããAPIã
- Feature PolicyïŒ WebããŒãžã§å©çšå¯èœãªãã©ãŠã¶ã®æ©èœãå¶åŸ¡ããã¡ã«ããºã ãããã«ãããã¢ããªã±ãŒã·ã§ã³ã®æ»æå¯Ÿè±¡é åãæžããããšãã§ããŸãã
- Subresource Integrity (SRI)ïŒ CDNããååŸãããã¡ã€ã«ãæ¹ãããããŠããªãããšãæ€èšŒããã¡ã«ããºã ã
- ãã詳现ãªãã£ã¬ã¯ãã£ãïŒ ãªãœãŒã¹ã®èªã¿èŸŒã¿ããã现ããå¶åŸ¡ããããã«ãããå ·äœçã§è©³çްãªCSPãã£ã¬ã¯ãã£ãã®ç¶ç¶çãªéçºã
çµè«
ããã³ããšã³ãã®ã³ã³ãã³ãã»ãã¥ãªãã£ããªã·ãŒéååæã¯ãçŸä»£ã®Webã¢ããªã±ãŒã·ã§ã³ã»ãã¥ãªãã£ã®äžå¯æ¬ ãªèŠçŽ ã§ããCSPéåãç©æ¥µçã«ç£èŠã»åæããããšã§ãæœåšçãªã»ãã¥ãªãã£ãªã¹ã¯ãç¹å®ããããªã·ãŒã埮調æŽããæ»æããã¢ããªã±ãŒã·ã§ã³ãä¿è·ããããšãã§ããŸããCSPãå®è£ ããéåã¬ããŒããç±å¿ã«åæããããšã¯ãã°ããŒãã«ãªèŠèŽè åãã®å®å šã§ä¿¡é Œæ§ã®é«ãWebã¢ããªã±ãŒã·ã§ã³ãæ§ç¯ããããã®éèŠãªã¹ãããã§ããèªååãããŒã æè²ãå«ããCSP管çãžã®ç©æ¥µçãªã¢ãããŒããåãå ¥ããããšã§ãé²åããè åšã«å¯Ÿããå ç¢ãªé²åŸ¡ãä¿èšŒãããŸããã»ãã¥ãªãã£ã¯ç¶ç¶çãªããã»ã¹ã§ãããCSPã¯ãã®ããã®åŒ·åãªããŒã«ã§ããããšãå¿ããªãã§ãã ããã